package com.handpay.zztong.hp.utils;

import android.content.Context;
import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.Bitmap.CompressFormat;
import android.graphics.Bitmap.Config;
import android.graphics.BitmapFactory;
import android.graphics.Color;
import android.graphics.Matrix;
import android.media.ThumbnailUtils;
import android.net.Uri;
import android.os.Environment;
import android.text.TextUtils;
import android.util.Base64;
import android.util.Log;
import android.view.View;

import com.handpay.framework.utils.CommonUtils;
import com.handpay.zztong.hp.log.HPLog;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.URI;

public class BitmapUtil {
    
	/*
     Resources res = getResources();
     Bitmap bmp = BitmapFactory.decodeResource(res, R.drawable.icon);
	 */


    
    public static byte[] Bitmap2Bytes(Bitmap bm) {
        if (null == bm) {
            return null;
        }
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        bm.compress(Bitmap.CompressFormat.PNG, 50, baos);
        return baos.toByteArray();
    }

    
    public static Bitmap bytes2Bimap(byte[] b) {
        if (b.length != 0) {
            return BitmapFactory.decodeByteArray(b, 0, b.length);
        } else {
            return null;
        }
    }

    
	public static void deleteFile(String signPath) {
        if (Environment.getExternalStorageState().equals(
                Environment.MEDIA_MOUNTED)) {
            File file = new File(signPath);
            if (file.exists()) {
                file.delete();
            } else {
            }
        } else {
        }
    }

    public static String createFile(Bitmap mSignBitmap) {
        ByteArrayOutputStream baos = null;
        String _path = null;
        try {
            String sign_dir = Environment.getExternalStorageDirectory()
                    + File.separator;
            _path = sign_dir + System.currentTimeMillis() + ".jpg";
            baos = new ByteArrayOutputStream();
            mSignBitmap.compress(Bitmap.CompressFormat.JPEG, 100, baos);
            byte[] photoBytes = baos.toByteArray();
            if (photoBytes != null) {
                new FileOutputStream(new File(_path)).write(photoBytes);
            }

        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            try {
                if (baos != null)
                    baos.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        return _path;
    }

    public static Bitmap compressImageQuality(Bitmap image, int quality) {
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        baos.reset();
        image.compress(Bitmap.CompressFormat.JPEG, quality, baos);
        ByteArrayInputStream isBm = new ByteArrayInputStream(baos.toByteArray());
        Bitmap bitmap = BitmapFactory.decodeStream(isBm, null, null);
        return bitmap;
    }

    
    public static Bitmap getBitmap(Bitmap image, double widthPixels, double heightPixels) {
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        image.compress(Bitmap.CompressFormat.JPEG, 100, baos);
        ByteArrayInputStream isBm = new ByteArrayInputStream(baos.toByteArray());
        BitmapFactory.Options newOpts = new BitmapFactory.Options();
        newOpts.inJustDecodeBounds = true;
        Bitmap bitmap = BitmapFactory.decodeStream(isBm, null, newOpts);
        newOpts.inJustDecodeBounds = false;
        int heightRatio = (int) Math.ceil(newOpts.outHeight / (heightPixels));
        int widthRatio = (int) Math.ceil(newOpts.outWidth / widthPixels);
        if (heightRatio > 1 || widthRatio > 1) {
            if (heightRatio > widthRatio) {
                newOpts.inSampleSize = heightRatio;
            } else {
                newOpts.inSampleSize = widthRatio;
            }
        }
        Log.i("", "getBitmap(Bitmap image...)" + newOpts.inSampleSize);
        isBm = new ByteArrayInputStream(baos.toByteArray());
        bitmap = BitmapFactory.decodeStream(isBm, null, newOpts);
        return bitmap;
    }

    
    public static Bitmap getBitmap(String imageFilePath, int widthPixels, int heightPixels) {
        int displayWidth = widthPixels;
        int displayHeight = heightPixels / 2;
        BitmapFactory.Options bmpFactoryOptions = new BitmapFactory.Options();
        bmpFactoryOptions.inJustDecodeBounds = true;
        Bitmap bmp = BitmapFactory.decodeFile(imageFilePath, bmpFactoryOptions);

        int heightRatio = (int) Math.ceil(bmpFactoryOptions.outHeight / displayHeight);
        int widthRatio = (int) Math.ceil(bmpFactoryOptions.outWidth / displayWidth);

        if (heightRatio > 1 || widthRatio > 1) {
            if (heightRatio > widthRatio) {
                bmpFactoryOptions.inSampleSize = heightRatio;
            } else {
                bmpFactoryOptions.inSampleSize = widthRatio;
            }
        }
        Log.i("", "getBitmap(String imageFilePath...)" + bmpFactoryOptions.inSampleSize);
        bmpFactoryOptions.inJustDecodeBounds = false;
        bmp = BitmapFactory.decodeFile(imageFilePath, bmpFactoryOptions);
        return bmp;
    }

    /***
     * 
     *
     * @param bgimage   
     * @param newWidth  
     * @param newHeight 
     * @return
     */
    public static Bitmap zoomImage(Bitmap bgimage, double newWidth, double newHeight) {        
        float width = bgimage.getWidth();
        float height = bgimage.getHeight();
        
        Matrix matrix = new Matrix();
        
        float scaleWidth = ((float) newWidth) / width;
        float scaleHeight = ((float) newHeight) / height;
        
        Log.i("", "zoomImage(Bitmap image...)" + scaleWidth);
        matrix.postScale(scaleWidth, scaleHeight);
        Bitmap bitmap = Bitmap.createBitmap(bgimage, 0, 0, (int) width, (int) height, matrix, true);
        return bitmap;
    }

    public static Bitmap getViewBitmap(View v) {
        v.clearFocus();
        v.setPressed(false);

        boolean willNotCache = v.willNotCacheDrawing();
        v.setWillNotCacheDrawing(false);

        // Reset the drawing cache background color to fully transparent  
        // for the duration of this operation  
        int color = v.getDrawingCacheBackgroundColor();
        v.setDrawingCacheBackgroundColor(0);

        if (color != 0) {
            v.destroyDrawingCache();
        }
        v.buildDrawingCache();
        Bitmap cacheBitmap = v.getDrawingCache();
        if (cacheBitmap == null) {            
            return null;
        }

        Bitmap bitmap = Bitmap.createBitmap(cacheBitmap);
        // Restore the view  
        v.destroyDrawingCache();
        v.setWillNotCacheDrawing(willNotCache);
        v.setDrawingCacheBackgroundColor(color);

        return bitmap;
    }

    public static int dip2px(Context context, float dipValue) {
        final float scale = context.getResources().getDisplayMetrics().density;
        return (int) (dipValue * scale + 0.5f);
    }

    public static int px2dip(Context context, float pxValue) {
        final float scale = context.getResources().getDisplayMetrics().density;
        Log.e("px2dip", "pxValue:" + pxValue + "scale:" + scale);
        return (int) (pxValue / scale + 0.5f);
    }

    /**
     * @param bmp
     * @return
     */
    public static Bitmap convertToBlackWhite(Bitmap bmp) {
        int width = bmp.getWidth(); 
        int height = bmp.getHeight();
        int[] pixels = new int[width * height]; 

        bmp.getPixels(pixels, 0, width, 0, 0, width, height);
        int alpha = 0xFF << 24;
        for (int i = 0; i < height; i++) {
            for (int j = 0; j < width; j++) {
                int grey = pixels[width * i + j];

                int red = ((grey & 0x00FF0000) >> 16);
                int green = ((grey & 0x0000FF00) >> 8);
                int blue = (grey & 0x000000FF);

                grey = (int) (red * 0.3 + green * 0.59 + blue * 0.11);
                grey = alpha | (grey << 16) | (grey << 8) | grey;
                pixels[width * i + j] = grey;
            }
        }
        Bitmap newBmp = Bitmap.createBitmap(width, height, Config.RGB_565);

        newBmp.setPixels(pixels, 0, width, 0, 0, width, height);

        Bitmap resizeBmp = ThumbnailUtils.extractThumbnail(newBmp, width, height);
        return resizeBmp;
    }

    public static byte[] saveBmpToJbg(Bitmap bitmap) {
          /*
  		 //
	 	    int nBmpWidth = bitmap.getWidth();  
	 	    int nBmpHeight = bitmap.getHeight();  
	 	    Log.i("bitmap", "width:" +nBmpWidth+"height"+nBmpHeight);
	 	    
	 	    int mBmpWidth = 0;
	 	    int mBmpHeight = nBmpHeight;
	 	    if (nBmpWidth %8 != 0)
	 	    {
	 	    	mBmpWidth += 1;
	 	    }
	 	    mBmpWidth += (nBmpWidth /8);	    
	 	    mBmpWidth += (mBmpWidth %4);
	 	    
	 	    
  		   byte[] bmpData = getBitmapData(bitmap);
  		   Log.i("BitmapUtilѹ��ǰ",62+bmpData.length+"B");
  		   //jbigUtils jbig = new jbigUtils();
           byte[] jbigBuffer = new byte[10000];
           int jbigBufferSize = jbig.jEncoder(mBmpWidth *8, mBmpHeight, 1, bmpData, jbigBuffer);
           byte[] jData = new byte[jbigBufferSize];
           System.arraycopy(jbigBuffer, 0, jData, 0, jbigBufferSize);
           jbigBuffer = null;
           Log.i("BitmapUtilѹ����",jData.length+"B");
  		 return jData;
  		 */
        return null;

    }

    public static Bitmap getBmpFromJbg(byte[] jbigData, int nBmpWidth, int nBmpHeight) {
  		/*
  		Bitmap bitmap = null;
  		byte[] bData = new byte[100000];
  		jbigUtils jbig = new jbigUtils();
  		Log.i("BitmapUtil��ѹǰ",jbigData.length+"B");
  		int jBmpSize = jbig.jDecoder(jbigData.length, jbigData, bData);
  		Log.i("BitmapUtil��ѹ��",62+jBmpSize+"B");
  		byte[] bmpData = new byte[jBmpSize+62];
  		System.arraycopy(getBmpHeader(nBmpWidth,nBmpHeight),0,bmpData,0,62);
        System.arraycopy(bData, 0, bmpData,62, jBmpSize);
  		bitmap = bytes2Bimap(bmpData);
  		Log.i("BitmapUtil","bitmap:" + bitmap+"("+bitmap.getWidth()+","+bitmap.getHeight()+")");
  		return bitmap;
  		*/
        return null;
    }

    public static byte[] getBmpHeader(int nBmpWidth, int nBmpHeight) {
        int mBmpWidth = 0;
        int mBmpHeight = nBmpHeight;
        if (nBmpWidth % 8 != 0) {
            mBmpWidth += 1;
        }
        mBmpWidth += (nBmpWidth / 8);
        mBmpWidth += (mBmpWidth % 4);
        int bufferSize = (mBmpWidth * mBmpHeight) + 2;
        byte[] bmpHeaderInfo = new byte[62];
        try {
            
            byte[] bmpHeader = bmpHeaderInfo;
            int pos = 0;
            
            int bfType = 0x4d42;
            long bfSize = 14 + 48 + bufferSize;
            int bfReserved1 = 0;
            int bfReserved2 = 0;
            long bfOffBits = 14 + 48;
            
            writeWord(bmpHeader, pos, bfType);
            pos += 2;

            writeDword(bmpHeader, pos, bfSize);
            pos += 4;

            writeWord(bmpHeader, pos, bfReserved1);
            pos += 2;

            writeWord(bmpHeader, pos, bfReserved2);
            pos += 2;

            writeDword(bmpHeader, pos, bfOffBits);
            pos += 4;
            
            long biSize = 40L;
            long biWidth = nBmpWidth;
            long biHeight = nBmpHeight;
            int biPlanes = 1;
            int biBitCount = 1;
            long biCompression = 0L;
            long biSizeImage = bufferSize;
            long biXpelsPerMeter = 2834L;
            long biYPelsPerMeter = 2834L;
            long biClrUsed = 0L;
            long biClrImportant = 0L;
            long color0 = 16777215L;
            long color1 = 0L;
            
            writeDword(bmpHeader, pos, biSize);
            pos += 4;
            writeLong(bmpHeader, pos, biWidth);
            pos += 4;
            writeLong(bmpHeader, pos, biHeight);
            pos += 4;
            writeWord(bmpHeader, pos, biPlanes);
            pos += 2;
            writeWord(bmpHeader, pos, biBitCount);
            pos += 2;
            writeDword(bmpHeader, pos, biCompression);
            pos += 4;
            writeDword(bmpHeader, pos, biSizeImage);
            pos += 4;
            writeLong(bmpHeader, pos, biXpelsPerMeter);
            pos += 4;
            writeLong(bmpHeader, pos, biYPelsPerMeter);
            pos += 4;
            writeDword(bmpHeader, pos, biClrUsed);
            pos += 4;
            writeDword(bmpHeader, pos, biClrImportant);
            pos += 4;
            writeDword(bmpHeader, pos, color1);
            pos += 4;
            writeDword(bmpHeader, pos, color0);
            pos += 4;
        } catch (Exception e) {
            e.printStackTrace();
        }
        return bmpHeaderInfo;
    }

    public static byte[] getBitmapData(Bitmap bitmap) {
        if (bitmap == null)
            return null;
        
        int nBmpWidth = bitmap.getWidth();
        int nBmpHeight = bitmap.getHeight();
        Log.i("bitmap", "width:" + nBmpWidth + "height" + nBmpHeight);
        
        int mBmpWidth = 0;
        int mBmpHeight = nBmpHeight;
        if (nBmpWidth % 8 != 0) {
            mBmpWidth += 1;
        }
        mBmpWidth += (nBmpWidth / 8);
        mBmpWidth += (mBmpWidth % 4);
        int bufferSize = (mBmpWidth * mBmpHeight) + 2;
        
        byte bmpData[] = new byte[bufferSize];
        for (int i = 0; i < bufferSize; ++i) {
            bmpData[i] = 0x00;
        }
        int wWidth = mBmpWidth;
        for (int nCol = 0, nRealCol = nBmpHeight - 1; nCol < nBmpHeight; ++nCol, --nRealCol) {
            int wByteIdex = 0;
            int nByte = 0;
            for (int wRow = 0; wRow < nBmpWidth; wRow++) {
                int clr = bitmap.getPixel(wRow, nCol);
                int red = Color.red(clr);
                int blue = Color.blue(clr);
                int green = Color.green(clr);

                if (red == 0 && blue == 0 && green == 0) {
                    bmpData[nRealCol * wWidth + wByteIdex] = (byte) (bmpData[nRealCol * wWidth + wByteIdex] << 1 & 0xff);
                } else {
                    bmpData[nRealCol * wWidth + wByteIdex] = (byte) (((bmpData[nRealCol * wWidth + wByteIdex] << 1) | 0x01) & 0xff);
                }
                nByte++;
                if (nByte == 8) {
                    nByte = 0;
                    wByteIdex++;
                }

            }

            if (nByte != 0) {
                for (; nByte < 8; ++nByte) {
                    bmpData[nRealCol * wWidth + wByteIdex] = (byte) (bmpData[nRealCol * wWidth + wByteIdex] << 1 & 0xff);
                }
            }
        }
        return bmpData;
    }

    /**
     *
     * @param bitmap
     */
    public static byte[] savaBitmapToBmp(Bitmap bitmap, String fileName) {
        if (bitmap == null)
            return null;
        Log.i("bitmap", "savaBitmapToBmp::width:" + bitmap.getWidth() + "height" + bitmap.getHeight());
        byte[] bmpHeader = getBmpHeader(bitmap.getWidth(), bitmap.getHeight());
        byte bmpData[] = getBitmapData(bitmap);
        byte[] bmp = new byte[bmpHeader.length + bmpData.length];
        try {
            Log.i("bitmap", "fileName:" + fileName);
            File file = new File(fileName);
            if (!file.exists()) {
                file.createNewFile();
            }
            FileOutputStream fileos = new FileOutputStream(fileName);
            fileos.write(bmpHeader);
            fileos.write(bmpData);
            fileos.flush();
            fileos.close();
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }
        return bmp;
    }

    protected static void writeWord(byte[] data, int pos, int value) throws IOException {
        byte[] b = new byte[2];
        b[0] = (byte) (value & 0xff);
        b[1] = (byte) (value >> 8 & 0xff);
        System.arraycopy(b, 0, data, pos, 2);
    }

    protected static void writeDword(byte[] data, int pos, long value) throws IOException {
        byte[] b = new byte[4];
        b[0] = (byte) (value & 0xff);
        b[1] = (byte) (value >> 8 & 0xff);
        b[2] = (byte) (value >> 16 & 0xff);
        b[3] = (byte) (value >> 24 & 0xff);

        System.arraycopy(b, 0, data, pos, 4);
    }

    protected static void writeLong(byte[] data, int pos, long value) throws IOException {
        byte[] b = new byte[4];
        b[0] = (byte) (value & 0xff);
        b[1] = (byte) (value >> 8 & 0xff);
        b[2] = (byte) (value >> 16 & 0xff);
        b[3] = (byte) (value >> 24 & 0xff);
        System.arraycopy(b, 0, data, pos, 4);
    }

    //***********************************
    private static void writeByte(FileOutputStream stream, int value)
            throws IOException {
        byte[] b = new byte[1];
        b[0] = (byte) (value & 0xff);
        stream.write(b);
    }

    private static void writeWord(FileOutputStream stream, int value)
            throws IOException {
        byte[] b = new byte[2];
        b[0] = (byte) (value & 0xff);
        b[1] = (byte) (value >> 8 & 0xff);
        stream.write(b);
    }

    private static void writeDword(FileOutputStream stream, long value)
            throws IOException {
        byte[] b = new byte[4];
        b[0] = (byte) (value & 0xff);
        b[1] = (byte) (value >> 8 & 0xff);
        b[2] = (byte) (value >> 16 & 0xff);
        b[3] = (byte) (value >> 24 & 0xff);
        stream.write(b);
    }

    private static void writeLong(FileOutputStream stream, long value)
            throws IOException {
        byte[] b = new byte[4];
        b[0] = (byte) (value & 0xff);
        b[1] = (byte) (value >> 8 & 0xff);
        b[2] = (byte) (value >> 16 & 0xff);
        b[3] = (byte) (value >> 24 & 0xff);
        stream.write(b);
    }


    
    public static void save1bBmpFile(Bitmap bitmap, String filename) {
        if (bitmap == null)
            return;
        // λͼ��С
        int nBmpWidth = bitmap.getWidth();
        int nBmpHeight = bitmap.getHeight();
        // ͼ�����ݴ�С
        int wid = nBmpWidth % 32;
        if (wid > 0) {
            wid = 32 - nBmpWidth % 32;
        }
        wid += nBmpWidth;

        int bufferSize = nBmpHeight * wid / 8;
        try {
            File file = new File(filename);
            if (!file.exists()) {
                file.createNewFile();
            }
            //file.deleteOnExit();
            FileOutputStream fileos = new FileOutputStream(filename);
            int bfType = 0x4d42;
            long bfSize = 14 + 40 + 2 * 4 + bufferSize;
            int bfReserved1 = 0;
            int bfReserved2 = 0;
            long bfOffBits = 14 + 40 + 2 * 4;
                        writeWord(fileos, bfType);
            writeDword(fileos, bfSize);
            writeWord(fileos, bfReserved1);
            writeWord(fileos, bfReserved2);
            writeDword(fileos, bfOffBits);
            
            long biSize = 40L;
            long biWidth = nBmpWidth;
            long biHeight = nBmpHeight;
            int biPlanes = 1;
            int biBitCount = 1;
            long biCompression = 0L;
            long biSizeImage = bufferSize;
            long biXpelsPerMeter = 0L;
            long biYPelsPerMeter = 0L;
            long biClrUsed = 0L;
            long biClrImportant = 2L;
            
            writeDword(fileos, biSize);
            writeLong(fileos, biWidth);
            writeLong(fileos, biHeight);
            writeWord(fileos, biPlanes);
            writeWord(fileos, biBitCount);
            writeDword(fileos, biCompression);
            writeDword(fileos, biSizeImage);
            writeLong(fileos, biXpelsPerMeter);
            writeLong(fileos, biYPelsPerMeter);
            writeDword(fileos, biClrUsed);
            writeDword(fileos, biClrImportant);

            
            byte rgbBlue0 = 0x0;
            byte rgbGreen0 = 0x0;
            byte rgbRed0 = 0x0;
            byte rgbReserved0 = 0x0;
            byte rgbBlue1 = (byte) 0xff;
            byte rgbGreen1 = (byte) 0xff;
            byte rgbRed1 = (byte) 0xff;
            byte rgbReserved1 = (byte) 0x00;
            
            writeByte(fileos, rgbBlue0);
            writeByte(fileos, rgbGreen0);
            writeByte(fileos, rgbRed0);
            writeByte(fileos, rgbReserved0);
            writeByte(fileos, rgbBlue1);
            writeByte(fileos, rgbGreen1);
            writeByte(fileos, rgbRed1);
            writeByte(fileos, rgbReserved1);

            
            byte bmpData[] = new byte[bufferSize];
            @SuppressWarnings("unused")
            int wWidth = (nBmpWidth * 3 + nBmpWidth % 4);
            @SuppressWarnings("unused")
            int index = 0;
            for (int nCol = 0; nCol < nBmpHeight; ++nCol) {
                for (int wRow = 0; wRow < nBmpWidth; ) {
                    int clr;
                    clr = bitmap.getPixel(wRow++, nCol);
                    int color0 = (Color.blue(clr) + Color.green(clr) + Color
                            .red(clr)) / 3 / 255 ^ 1;

                    clr = bitmap.getPixel(wRow++, nCol);
                    int color1 = (Color.blue(clr) + Color.green(clr) + Color
                            .red(clr)) / 3 / 255 ^ 1;

                    clr = bitmap.getPixel(wRow++, nCol);
                    int color2 = (Color.blue(clr) + Color.green(clr) + Color
                            .red(clr)) / 3 / 255 ^ 1;

                    clr = bitmap.getPixel(wRow++, nCol);
                    int color3 = (Color.blue(clr) + Color.green(clr) + Color
                            .red(clr)) / 3 / 255 ^ 1;

                    clr = bitmap.getPixel(wRow++, nCol);
                    int color4 = (Color.blue(clr) + Color.green(clr) + Color
                            .red(clr)) / 3 / 255 ^ 1;

                    clr = bitmap.getPixel(wRow++, nCol);
                    int color5 = (Color.blue(clr) + Color.green(clr) + Color
                            .red(clr)) / 3 / 255 ^ 1;

                    clr = bitmap.getPixel(wRow++, nCol);
                    int color6 = (Color.blue(clr) + Color.green(clr) + Color
                            .red(clr)) / 3 / 255 ^ 1;

                    clr = bitmap.getPixel(wRow, nCol);
                    int color7 = (Color.blue(clr) + Color.green(clr) + Color
                            .red(clr)) / 3 / 255 ^ 1;

            
                    bmpData[nCol * (wid / 8) + wRow++ / 8] = (byte) ((color0 << 7)
                            | (color1 << 6)
                            | (color2 << 5)
                            | (color3 << 4)
                            | (color4 << 3) | (color5 << 2) | (color6 << 1) | (color7));

                }
            }

            fileos.write(bmpData);
            fileos.flush();
            fileos.close();
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    
    public void save1bBmpxFile(Bitmap bitmap, String filename) {
        if (bitmap == null)
            return;
    
        int nBmpWidth = bitmap.getWidth();
        int nBmpHeight = bitmap.getHeight();
    
        int wid = nBmpWidth % 32;
        if (wid > 0) {
            wid = 32 - nBmpWidth % 32;
        }
        wid += nBmpWidth;

        int bufferSize = nBmpHeight * wid / 8;
        try {
            
            File file = new File(filename);
            if (!file.exists()) {
                file.createNewFile();
            }
            FileOutputStream fileos = new FileOutputStream(filename);
            
            int bfType = 0x4d42;
            long bfSize = 14 + 40 + 2 * 4 + bufferSize;
            int bfReserved1 = 0;
            int bfReserved2 = 0;
            long bfOffBits = 14 + 40 + 2 * 4;
            
            writeWord(fileos, bfType);
            writeDword(fileos, bfSize);
            writeWord(fileos, bfReserved1);
            writeWord(fileos, bfReserved2);
            writeDword(fileos, bfOffBits);
            
            long biSize = 40L;
            long biWidth = nBmpWidth;
            long biHeight = nBmpHeight;
            int biPlanes = 1;
            int biBitCount = 1;
            long biCompression = 0L;
            long biSizeImage = bufferSize;
            long biXpelsPerMeter = 0L;
            long biYPelsPerMeter = 0L;
            long biClrUsed = 0L;
            long biClrImportant = 2L;
            
            writeDword(fileos, biSize);
            writeLong(fileos, biWidth);
            writeLong(fileos, biHeight);
            writeWord(fileos, biPlanes);
            writeWord(fileos, biBitCount);
            writeDword(fileos, biCompression);
            writeDword(fileos, biSizeImage);
            writeLong(fileos, biXpelsPerMeter);
            writeLong(fileos, biYPelsPerMeter);
            writeDword(fileos, biClrUsed);
            writeDword(fileos, biClrImportant);

            
            byte rgbBlue0 = 0x0;
            byte rgbGreen0 = 0x0;
            byte rgbRed0 = 0x0;
            byte rgbReserved0 = 0x0;
            byte rgbBlue1 = (byte) 0xff;
            byte rgbGreen1 = (byte) 0xff;
            byte rgbRed1 = (byte) 0xff;
            byte rgbReserved1 = (byte) 0x00;
            
            writeByte(fileos, rgbBlue0);
            writeByte(fileos, rgbGreen0);
            writeByte(fileos, rgbRed0);
            writeByte(fileos, rgbReserved0);
            writeByte(fileos, rgbBlue1);
            writeByte(fileos, rgbGreen1);
            writeByte(fileos, rgbRed1);
            writeByte(fileos, rgbReserved1);

            
            byte bmpData[] = new byte[bufferSize];
            @SuppressWarnings("unused")
            int wWidth = (nBmpWidth * 3 + nBmpWidth % 4);
            @SuppressWarnings("unused")
            int index = 0;
            for (int nCol = 0, nRealCol = nBmpHeight - 1; nCol < nBmpHeight; ++nCol, --nRealCol) {
                for (int wRow = 0; wRow < nBmpWidth; ) {
                    int clr;
                    clr = bitmap.getPixel(wRow++, nCol);
                    int color0 = (Color.blue(clr) + Color.green(clr) + Color
                            .red(clr)) / 3 / 200;

                    clr = bitmap.getPixel(wRow++, nCol);
                    int color1 = (Color.blue(clr) + Color.green(clr) + Color
                            .red(clr)) / 3 / 200;

                    clr = bitmap.getPixel(wRow++, nCol);
                    int color2 = (Color.blue(clr) + Color.green(clr) + Color
                            .red(clr)) / 3 / 200;

                    clr = bitmap.getPixel(wRow++, nCol);
                    int color3 = (Color.blue(clr) + Color.green(clr) + Color
                            .red(clr)) / 3 / 200;

                    clr = bitmap.getPixel(wRow++, nCol);
                    int color4 = (Color.blue(clr) + Color.green(clr) + Color
                            .red(clr)) / 3 / 200;

                    clr = bitmap.getPixel(wRow++, nCol);
                    int color5 = (Color.blue(clr) + Color.green(clr) + Color
                            .red(clr)) / 3 / 200;

                    clr = bitmap.getPixel(wRow++, nCol);
                    int color6 = (Color.blue(clr) + Color.green(clr) + Color
                            .red(clr)) / 3 / 200;

                    clr = bitmap.getPixel(wRow, nCol);
                    int color7 = (Color.blue(clr) + Color.green(clr) + Color
                            .red(clr)) / 3 / 200;

            
                    bmpData[nRealCol * (wid / 8) + wRow++ / 8] = (byte) ((color0 << 7)
                            | (color1 << 6)
                            | (color2 << 5)
                            | (color3 << 4)
                            | (color4 << 3) | (color5 << 2) | (color6 << 1) | (color7));

                }
            }

            fileos.write(bmpData);
            fileos.flush();
            fileos.close();

        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    public static String bitmapToBase64(Bitmap bitmap) {
        String string = null;
        ByteArrayOutputStream bStream = new ByteArrayOutputStream();
        bitmap.compress(CompressFormat.PNG, 100, bStream);
        byte[] bytes = bStream.toByteArray();
        string = Base64.encodeToString(bytes, Base64.DEFAULT);
        return string;
    }

    public static final String root = Environment.getExternalStorageDirectory() + "/zzTong/cardImg/";
    public static final String trimed_card_img = CommonUtils.getAccessImgDir().getAbsolutePath() + "/trimed_card_img.jpg";
    public static final String origianl_card_img = CommonUtils.getAccessImgDir().getAbsolutePath() + "/origianl_card_img.jpg";

    /***
     * 根据文件名保存文件
     *
     * @param data
     * @param filename
     * @return
     */
    public static String saveByte_File(byte[] data, String filename, Context context) {
        if (TextUtils.isEmpty(filename)) {
            return saveByte_File(data);
        } else {
            //1保存图片
            String path = root + filename + ".jpg";
            try {
                if (Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)) {
                    // 判断SD卡上是否有足够的空间
                    // String storage =
                    // Environment.getExternalStorageDirectory().toString();
                    // StatFs fs = new StatFs(storage);
                    // long available = fs.getAvailableBlocks() * fs.getBlockSize();
                    // if (available < data.length) {
                    // // 空间不足直接返回空
                    // return null;
                    // }
                    File dirs = new File(root);

                    if (!dirs.exists()) {
                        dirs.mkdirs();
                    } else {
                        File[] files = dirs.listFiles();
                        HPLog.e(HPLog.FDL_TAG, "files.len=" + files.length);
                        for (File file : files) {
                            HPLog.e(HPLog.FDL_TAG, "fileName=" + file.getName());
                            boolean isDelete = file.delete();
                            HPLog.e(HPLog.FDL_TAG, "isDelete=" + isDelete);
                        }
                    }
                    File file = new File(path);
                    if (!file.exists())
                        // 创建文件
                        file.createNewFile();
                    FileOutputStream fos = new FileOutputStream(file);
                    fos.write(data);
                    fos.close();
                    //2.往手机系统插入保存的图片
//					try {
//						MediaStore.Images.Media.insertImage(context.getContentResolver(),
//								file.getAbsolutePath(), filename+".jpg", null);
//					} catch (FileNotFoundException e) {
//						e.printStackTrace();
//					}
                    // 最后通知图库更新
                    context.sendBroadcast(new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, Uri.parse("file://" + path)));
                }
            } catch (Exception e) {
                e.printStackTrace();
                return null;
            }
            return path;
        }
    }

    /**
     * @param data
     * @param bAutoDelFile
     * @return
     */
    public static String saveByte_File(byte[] data, boolean bAutoDelFile) {
        String path = root + System.currentTimeMillis() + ".jpg";
        try {
            if (Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)) {
                // 判断SD卡上是否有足够的空间
                // String storage =
                // Environment.getExternalStorageDirectory().toString();
                // StatFs fs = new StatFs(storage);
                // long available = fs.getAvailableBlocks() * fs.getBlockSize();
                // if (available < data.length) {
                // // 空间不足直接返回空
                // return null;
                // }
                File dirs = new File(root);

                if (!dirs.exists()) {
                    dirs.mkdirs();
                } else {
                    if (bAutoDelFile) {
                        File[] files = dirs.listFiles();
                        for (File file : files) {
                            boolean isDelete = file.delete();
                        }
                    }
                }
                File file = new File(path);
                if (!file.exists())
                    file.createNewFile();
                FileOutputStream fos = new FileOutputStream(file);
                fos.write(data);
                fos.close();
            }
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
        return path;
    }


    /***
     * 保存文件
     * @param data
     * @return
     */
    public static String saveByte_File(byte[] data) {
        return saveByte_File(data, true);
    }

    public static void deleteICImgsdir() {
        try {
            File fileroot = new File(root);
            if (fileroot.exists() && fileroot.isDirectory()) {
                File[] files = fileroot.listFiles();
                for (File file : files) {
                    file.delete();
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    public static byte[] getFileByteToSDC(String FileUrl) {
        byte[] in2b = null;
        InputStream fos = null;
        ByteArrayOutputStream swapStream = null;
        try {
            if (FileUrl != null && FileUrl.length() > 0 && Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)) {
                File dirs = null;
                if (FileUrl.startsWith("file:///")) {
                    dirs = new File(URI.create(FileUrl));
                } else {
                    dirs = new File(FileUrl);
                }
                if (!dirs.exists()) {
                    HPLog.e(HPLog.FDL_TAG, "该文件不存在 =" + FileUrl);
                    return null;
                }
                fos = new FileInputStream(dirs);
				/*byte[] buffer = new byte[fos.available()];
				fos.read(buffer);*/
                swapStream = new ByteArrayOutputStream();
                byte[] buff = new byte[1024];
                int rc = 0;
                while ((rc = fos.read(buff)) != -1) {
                    swapStream.write(buff, 0, rc);
                }
                in2b = swapStream.toByteArray();
            }
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        } finally {
            try {
                if (fos != null) {
                    fos.close();
                }
                if (swapStream != null) {
                    swapStream.close();
                }
            } catch (IOException e) {
                e.printStackTrace();
            }

        }

        return in2b;
    }

    /**
     * 无损压缩图片
     *
     * @param bm
     * @return
     */
    public static byte[] Bitmap2BytesCrop(Bitmap bm) {
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        bm.compress(Bitmap.CompressFormat.JPEG, 100, baos);
        int options = 100;
        while (baos.toByteArray().length / 1024 > 200) {
            baos.reset();
            if (options <= 0) {
                options = 80;
            }
            bm.compress(Bitmap.CompressFormat.JPEG, options, baos);
            options -= 9;
        }
        return baos.toByteArray();
    }
}
